home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Almathera Ten Pack 3: CDPD 3
/
Almathera Ten on Ten - Disc 3: CDPD3.iso
/
fish
/
676-700
/
681
/
term
/
source.lha
/
ParseCode.c
< prev
next >
Wrap
C/C++ Source or Header
|
1992-05-09
|
9KB
|
389 lines
/*
** $Id: ParseCode.c,v 1.4 92/04/21 16:59:12 olsen Sta Locker: olsen $
** $Revision: 1.4 $
** $Date: 92/04/21 16:59:12 $
**
** ANSI control code parsing routines
**
** Copyright © 1990-1992 by Olaf `Olsen' Barthel & MXM
** All Rights Reserved
*/
#include "termGlobal.h"
/* How many characters we will keep in the scan buffer. */
#define MAX_SCAN_SIZE 40
/* A couple of internally referenced variables. */
STATIC BYTE CharsInBuffer = 0,
ScanStep = 0;
STATIC UBYTE SaveBuffer[MAX_SCAN_SIZE * 2];
/* Character access tables. */
STATIC UBYTE Table1[256] =
{
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
1,1,1,1,1,1,1,1,1,1,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
};
STATIC UBYTE Table2[256] =
{
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
1,1,1,1,1,1,1,1,1,1,0,1,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
};
STATIC UBYTE Table3[256] =
{
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
1,1,1,1,1,1,1,1,1,1,0,0,0,0,0,1,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
};
STATIC UBYTE Table4[256] =
{
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
1,1,1,1,1,1,1,1,1,1,0,0,0,1,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0
};
/* This structure describes an ANSI control sequence. */
struct ControlCode
{
UBYTE FirstChar;
UBYTE *Match;
UBYTE LastChar;
BYTE ExactSize;
UBYTE * (* __regargs Func)(UBYTE *Buffer);
};
#define NUM_CODES (sizeof(ANSICode) / sizeof(struct ControlCode))
/* This follows the control code information. */
struct ControlCode ANSICode[] =
{
/* Single Character Sequences. */
'D', NULL, 0 , 1, (APTR)CursorScrollDown,
'M', NULL, 0 , 1, (APTR)CursorScrollUp,
'E', NULL, 0 , 1, (APTR)NextLine,
'7', NULL, 0 , 1, (APTR)SaveCursor,
'8', NULL, 0 , 1, (APTR)LoadCursor,
'=', NULL, 0 , 1, (APTR)NumericAppMode,
'>', NULL, 0 , 1, (APTR)NumericAppMode,
'N', NULL, 0 , 1, (APTR)Ignore,
'O', NULL, 0 , 1, (APTR)Ignore,
'H', NULL, 0 , 1, (APTR)SetTab,
'Z', NULL, 0 , 1, (APTR)RequestTerminal,
'c', NULL, 0 , 1, (APTR)Reset,
'<', NULL, 0 , 1, (APTR)Ignore,
'~', NULL, 0 , 1, (APTR)Ignore,
'n', NULL, 0 , 1, (APTR)Ignore,
'}', NULL, 0 , 1, (APTR)Ignore,
'o', NULL, 0 , 1, (APTR)Ignore,
'|', NULL, 0 , 1, (APTR)Ignore,
/* Double Character Sequences. */
'[', NULL, 's', 2, (APTR)SaveCursor,
'[', NULL, 'u', 2, (APTR)LoadCursor,
'(', NULL, 'A', 2, (APTR)FontStuff,
'(', NULL, 'B', 2, (APTR)FontStuff,
'(', NULL, '0', 2, (APTR)FontStuff,
')', NULL, 'A', 2, (APTR)FontStuff,
')', NULL, 'B', 2, (APTR)FontStuff,
')', NULL, '0', 2, (APTR)FontStuff,
'#', NULL, '3', 2, (APTR)ScaleFont,
'#', NULL, '4', 2, (APTR)ScaleFont,
'#', NULL, '5', 2, (APTR)ScaleFont,
'#', NULL, '6', 2, (APTR)ScaleFont,
'#', NULL, '8', 2, (APTR)AlignmentTest,
' ', NULL, 'F', 2, (APTR)Ignore,
' ', NULL, 'G', 2, (APTR)Ignore,
/* Multiple Character Sequence. */
'[', Table3, 'i', 0, (APTR)PrinterController,
'[', Table3, 'n', 0, (APTR)RequestInformation,
'[', Table3, 'c', 0, (APTR)RequestTerminal,
'[', Table3, 'h', 0, (APTR)SetSomething,
'[', Table3, 'l', 0, (APTR)SetSomething,
'[', Table4, 'h', 0, (APTR)Ignore,
'[', Table1, 'A', 0, (APTR)MoveCursor,
'[', Table1, 'B', 0, (APTR)MoveCursor,
'[', Table1, 'C', 0, (APTR)MoveCursor,
'[', Table1, 'D', 0, (APTR)MoveCursor,
'[', Table1, 'K', 0, (APTR)EraseLine,
'[', Table1, 'J', 0, (APTR)EraseScreen,
'[', Table1, 'P', 0, (APTR)EraseCharacters,
'[', Table1, 'L', 0, (APTR)InsertLine,
'[', Table1, 'M', 0, (APTR)ClearLine,
'[', Table1, 'g', 0, (APTR)SetTabs,
'[', Table1, 'q', 0, (APTR)Ignore,
'[', Table2, 'H', 0, (APTR)SetAbsolutePosition,
'[', Table2, 'f', 0, (APTR)SetAbsolutePosition,
'[', Table2, 'm', 0, (APTR)SetAttributes,
'[', Table2, 'y', 0, (APTR)Ignore,
'[', Table2, 'r', 0, (APTR)SetRegion,
'[', Table1, 'S', 0, (APTR)ScrollUp,
'[', Table1, 'T', 0, (APTR)ScrollDown
};
/* DoCancel():
*
* Cancel any currently scanned sequence.
*/
VOID
DoCancel()
{
InSequence = FALSE;
CharsInBuffer = ScanStep = 0;
}
/* CSIFake():
*
* This routine was added to support 8-bit control
* sequences introduced by a CSI character.
*/
VOID
CSIFake()
{
/* Reset scanner */
DoCancel();
/* Perform as if ESC [ had been transmitted. */
InSequence = ParseCode('[');
}
/* ParseCode(UBYTE c):
*
* Input: A character to be passed through the ANSI code
* parser.
*
* Output: FALSE if input characters did form a valid ANSI
* control sequence or if input characters did not
* form an ANSI control sequence at all.
*
* TRUE if input characters did possibly introduce
* a valid ANSI control sequence.
*/
BYTE __regargs
ParseCode(UBYTE c)
{
WORD i;
/* ScanStep = 0: This is the first character
* to introduce a control sequence.
*/
if(!ScanStep)
{
/* Scan all available codes and try to find
* a match.
*/
for(i = 0 ; i < NUM_CODES ; i++)
{
/* This character may introduce a
* control sequence.
*/
if(ANSICode[i] . FirstChar == c)
{
/* If this is a single
* character control sequence
* call the approriate function
* and exit immediately.
*/
if(ANSICode[i] . ExactSize == 1)
{
if(Config . Emulation != EMULATION_ATOMIC || Escape)
{
UBYTE *SomeString;
SaveBuffer[CharsInBuffer++] = c;
SaveBuffer[CharsInBuffer ] = 0;
if(SomeString = (*ANSICode[i] . Func)(SaveBuffer))
SerWrite(SomeString,strlen(SomeString));
}
CharsInBuffer = ScanStep = 0;
return(FALSE);
}
/* The length of this control
* sequence is greater than
* a single character. Save
* the input character and
* return.
*/
ScanStep = i;
SaveBuffer[CharsInBuffer++] = c;
return(TRUE);
}
}
/* No control sequence introducing character
* was found.
*/
CharsInBuffer = ScanStep = 0;
return(FALSE);
}
else
{
/* Length of the control sequence
* overrides the boundary, exit
* immediately!
*/
if(CharsInBuffer > MAX_SCAN_SIZE)
{
/* No Match */
CharsInBuffer = ScanStep = 0;
return(FALSE);
}
/* Scan the remaining codes for a match. */
for(i = ScanStep ; i < NUM_CODES ; i++)
{
/* This sequence begins with the
* same character the parser was
* initialized with, so let's take
* a look at it.
*/
if(ANSICode[i] . FirstChar == SaveBuffer[0])
{
/* This character is supposed to
* terminate the sequence, so exit.
*/
if(ANSICode[i] . LastChar == c)
{
if(Config . Emulation != EMULATION_ATOMIC || Escape)
{
UBYTE *SomeString;
SaveBuffer[CharsInBuffer++] = c;
SaveBuffer[CharsInBuffer ] = 0;
if(SomeString = (*ANSICode[i] . Func)(SaveBuffer))
SerWrite(SomeString,strlen(SomeString));
}
CharsInBuffer = ScanStep = 0;
return(FALSE);
}
else
{
if(ANSICode[i] . Match)
{
/* This character is part of
* a legal sequence. Store it
* and return.
*/
if(ANSICode[i] . Match[c])
{
ScanStep = i;
SaveBuffer[CharsInBuffer++] = c;
return(TRUE);
}
}
}
}
}
/* This character is not part of a valid
* ANSI control sequence, so exit.
*/
CharsInBuffer = ScanStep = 0;
return(FALSE);
}
}